package logic.weapons.projectileWeapons;

import fileHandling.ModelImporter;
import logic.ships.Ship;
import logic.weapons.Weapon;
import logic.weapons.WeaponFire;
import logic.weapons.WeaponType;
import main.listeners.ListenerContainer;

import com.jme.math.Vector3f;
import com.jme.scene.Node;

public abstract class ProjectileWeapon extends Weapon {
	
	private static final long serialVersionUID = 1L;
	
	private int projectilesLeft;
	private String projectilePath;
	private ListenerContainer projectileListeners;
	
	public ProjectileWeapon(Node model, String path, String title, ProjectileProperties properties, Ship ship) {
		super(model, path, title, properties, ship);
		projectilePath = properties.getProjectileType();
		projectilesLeft = properties.getMaxProjectiles();
		
		removeController(weaponController);
		weaponController = new ProjectileWeaponController(this);
		addController(weaponController);
		
		projectileListeners = new ListenerContainer(ProjectileListener.class);
	}
	
	public void addProjectileListener(ProjectileListener l) { projectileListeners.addListener(l); }
	
	public void removeProjectileListener(ProjectileListener l) { projectileListeners.removeListener(l); }
	
	protected void updateProjectiles(int amount) {
		if(projectilesLeft == amount) return;
		
		int old = projectilesLeft;
		projectilesLeft = amount;
		
		ProjectileChangedEvent event = new ProjectileChangedEvent(this, old, projectilesLeft);
		projectileListeners.callMethod(ProjectileListener.PROJECTILESCHANGED, event);
	}
	
	@Override
	public WeaponFire fire(Vector3f direction) {
		WeaponFire weaponFire = super.fire(direction);
		if(weaponFire != null) updateProjectiles(projectilesLeft - 1);
		return weaponFire;
	}
	
	@Override
	public WeaponFire getNewWeaponFire(Vector3f direction, Vector3f startLoc, boolean dummy) {
		Node model = ModelImporter.getModel(projectilePath, "");
		model.setLocalScale(0.2f);
		return createProjectile(direction, model, startLoc, dummy);
	}
	
	protected abstract Projectile createProjectile(Vector3f direction, Node projectileModel, Vector3f startLoc, boolean dummy);
	
	public boolean isFullyLoaded() { return projectilesLeft == getMaxProjectiles(); }
	
	public void addProjectile() {
		assert(!isFullyLoaded());
		updateProjectiles(projectilesLeft + 1);
	}
	
	public void reloadFully() {
		updateProjectiles(getMaxProjectiles());
	}
	
	public int getProjectilesLeft() { return projectilesLeft; }
	
	public int getMaxProjectiles() { return getProjectileWeaponProps().getMaxProjectiles(); }
	
	public boolean hasProjectiles() { return projectilesLeft > 0; }
	
	public ProjectileProperties getProjectileWeaponProps() { return (ProjectileProperties)properties; }
	
	public String getProjectilePath() { return projectilePath; }
	
	@Override
	public ListenerContainer getListenerContainer(Class<?> listenerClass) {
		if(listenerClass == ProjectileListener.class) return projectileListeners;
		return super.getListenerContainer(listenerClass);
	}
	
	public static int getProjectileCosts(WeaponType type) {
		switch(type) {
			case HeatSeeker: return 20;
			case Missile: return 15;
		}
		return 0;
	}
}